package com.rickpan.controller;

import com.rickpan.dto.common.ApiResponse;
import com.rickpan.service.CaptchaService;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.tags.Tag;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.*;

import javax.imageio.ImageIO;
import java.awt.image.BufferedImage;
import java.io.IOException;
import java.util.HashMap;
import java.util.Map;
import java.util.UUID;

/**
 * 验证码控制器
 */
@RestController
@RequestMapping("/api/captcha")
@RequiredArgsConstructor
@Slf4j
@Tag(name = "验证码管理", description = "验证码生成和验证接口")
public class CaptchaController {

    private final CaptchaService captchaService;

    /**
     * 生成验证码
     */
    @GetMapping("/generate")
    @Operation(summary = "生成验证码", description = "生成新的验证码，返回验证码ID")
    public ApiResponse<Map<String, Object>> generateCaptcha(HttpServletRequest request) {
        try {
            // 使用session ID或生成UUID作为验证码标识
            String sessionId = request.getSession().getId();
            if (sessionId == null || sessionId.isEmpty()) {
                sessionId = UUID.randomUUID().toString();
            }
            
            // 生成验证码
            String code = captchaService.generateCaptcha(sessionId);
            
            Map<String, Object> result = new HashMap<>();
            result.put("captchaId", sessionId);
            result.put("expireTime", 300); // 5分钟过期时间（秒）
            
            // 开发环境下返回验证码（生产环境应该移除）
            if (log.isDebugEnabled()) {
                result.put("code", code); // 仅用于调试
            }
            
            log.info("生成验证码成功: captchaId={}", sessionId);
            return ApiResponse.success("验证码生成成功", result);
            
        } catch (Exception e) {
            log.error("生成验证码失败", e);
            return ApiResponse.error("验证码生成失败");
        }
    }

    /**
     * 验证验证码
     */
    @PostMapping("/validate")
    @Operation(summary = "验证验证码", description = "验证用户输入的验证码是否正确")
    public ApiResponse<String> validateCaptcha(
            @Parameter(description = "验证码ID") @RequestParam String captchaId,
            @Parameter(description = "用户输入的验证码") @RequestParam String code) {
        
        try {
            boolean isValid = captchaService.validateCaptcha(captchaId, code);
            
            if (isValid) {
                log.info("验证码验证成功: captchaId={}", captchaId);
                return ApiResponse.success("验证码正确");
            } else {
                log.warn("验证码验证失败: captchaId={}, code={}", captchaId, code);
                return ApiResponse.error("验证码错误或已过期");
            }
            
        } catch (Exception e) {
            log.error("验证验证码失败: captchaId={}", captchaId, e);
            return ApiResponse.error("验证码验证失败");
        }
    }

    /**
     * 生成验证码图片（可选功能）
     */
    @GetMapping("/image")
    @Operation(summary = "生成验证码图片", description = "生成验证码图片，返回PNG格式图片")
    public void generateCaptchaImage(
            @Parameter(description = "验证码ID") @RequestParam String captchaId,
            HttpServletResponse response) throws IOException {
        
        try {
            // 生成新的验证码
            String code = captchaService.generateCaptcha(captchaId);
            
            // 生成验证码图片
            BufferedImage image = captchaService.generateCaptchaImage(code);
            
            // 设置响应头
            response.setContentType("image/png");
            response.setHeader("Cache-Control", "no-cache, no-store, must-revalidate");
            response.setHeader("Pragma", "no-cache");
            response.setDateHeader("Expires", 0);
            
            // 输出图片
            ImageIO.write(image, "PNG", response.getOutputStream());
            response.getOutputStream().flush();
            
            log.info("生成验证码图片成功: captchaId={}", captchaId);
            
        } catch (Exception e) {
            log.error("生成验证码图片失败: captchaId={}", captchaId, e);
            response.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
        }
    }

    /**
     * 刷新验证码
     */
    @PostMapping("/refresh")
    @Operation(summary = "刷新验证码", description = "刷新指定ID的验证码")
    public ApiResponse<Map<String, Object>> refreshCaptcha(
            @Parameter(description = "验证码ID") @RequestParam String captchaId) {
        
        try {
            // 删除旧验证码
            captchaService.removeCaptcha(captchaId);
            
            // 生成新验证码
            String code = captchaService.generateCaptcha(captchaId);
            
            Map<String, Object> result = new HashMap<>();
            result.put("captchaId", captchaId);
            result.put("expireTime", 300);
            
            // 开发环境下返回验证码
            if (log.isDebugEnabled()) {
                result.put("code", code);
            }
            
            log.info("刷新验证码成功: captchaId={}", captchaId);
            return ApiResponse.success("验证码刷新成功", result);
            
        } catch (Exception e) {
            log.error("刷新验证码失败: captchaId={}", captchaId, e);
            return ApiResponse.error("验证码刷新失败");
        }
    }

    /**
     * 获取验证码状态
     */
    @GetMapping("/status")
    @Operation(summary = "获取验证码状态", description = "获取验证码是否存在及剩余时间")
    public ApiResponse<Map<String, Object>> getCaptchaStatus(
            @Parameter(description = "验证码ID") @RequestParam String captchaId) {
        
        try {
            boolean exists = captchaService.existsCaptcha(captchaId);
            long expireTime = captchaService.getCaptchaExpireTime(captchaId);
            
            Map<String, Object> result = new HashMap<>();
            result.put("exists", exists);
            result.put("expireTime", expireTime);
            
            return ApiResponse.success("获取验证码状态成功", result);
            
        } catch (Exception e) {
            log.error("获取验证码状态失败: captchaId={}", captchaId, e);
            return ApiResponse.error("获取验证码状态失败");
        }
    }
}
